package com.wg.net;

import cn.hutool.core.util.StrUtil;

import java.util.Map;

import com.wg.net.operations.base.OperationRequest;
import com.wg.net.operations.base.OperationResponse;
import com.wg.net.operations.base.S2SOperationRequest;
import com.wg.net.operations.base.S2SOperationResponse;

/**
 * 内部错误码（标准化错误定义）
 * 
 * @author 少爷123
 */
public enum InnerErrorCode {
    /** 未知操作码 */
    OPERATION_UNKNOWN((short) (Short.MAX_VALUE - 1),
            "未知操作码: {opCode}, 客户端: {clientId}",
            "检查客户端是否更新了协议版本"),

    /** 请求格式错误 */
    REQUEST_FORMAT_ERROR((short) (Short.MAX_VALUE - 2),
            "请求格式错误: {opCode}, 错误: {error}",
            "验证请求数据结构体是否匹配协议"),

    /** 服务端内部错误 */
    INTERNAL_SERVER_ERROR((short) (Short.MAX_VALUE - 3),
            "服务端内部错误: {handler}[{opCode}], 异常: {exception}",
            "检查服务器日志获取详细堆栈"),

    /** 发送失败 */
    NETWORK_SEND_FAIL((short) (Short.MAX_VALUE - 4),
            "网络发送失败: 目标={target}, 原因={reason}",
            "检查网络连接或目标服务状态"),

    /** 处理超时 */
    PROCESS_TIMEOUT((short) (Short.MAX_VALUE - 5),
            "请求处理超时: 处理器={handler}, 耗时={elapsedMs}ms",
            "优化业务逻辑或增加超时阈值");

    private final short code;
    private final String template;
    private final String solution;

    /**
     * 错误码构造函数
     * 
     * @param code     错误码（唯一标识）
     * @param template 错误信息模板（支持占位符）
     * @param solution 解决方案提示
     */
    InnerErrorCode(short code, String template, String solution) {
        this.code = code;
        this.template = template;
        this.solution = solution;
    }

    public short getCode() {
        return code;
    }

    /**
     * 构建完整错误信息
     *
     * @param context 错误上下文键值对
     * @return 格式化后的错误信息
     */
    public String getMessage(Map<String, Object> context) {
        return formatTemplate(template, context) + " | 解决方案: " + solution;
    }

    /**
     * 为S2S请求构建错误响应
     *
     * @param request 原始请求
     * @param context 错误上下文
     * @return 标准错误响应对象
     */
    public S2SOperationResponse buildS2SResponse(S2SOperationRequest request,
            Map<String, Object> context) {
        return ErrorHelper.buildS2SResponse(request, code, getMessage(context));
    }

    /**
     * 为客户端请求构建错误响应
     *
     * @param request 原始请求
     * @param context 错误上下文
     * @return 标准错误响应对象
     */
    public OperationResponse buildResponse(OperationRequest request,
            Map<String, Object> context) {
        return ErrorHelper.buildResponse(request, code, getMessage(context));
    }

    /**
     * 快速构建错误响应（简化版）
     *
     * @param request 原始请求
     * @param args    错误信息占位符参数
     * @return 标准错误响应对象
     */
    public OperationResponse quickResponse(OperationRequest request, Object... args) {
        return ErrorHelper.buildResponse(request, code, StrUtil.format(template, args));
    }

    /**
     * 快速构建S2S错误响应（简化版）
     *
     * @param request 原始请求
     * @param args    错误信息占位符参数
     * @return 标准错误响应对象
     */
    public S2SOperationResponse quickS2SResponse(S2SOperationRequest request, Object... args) {
        return ErrorHelper.buildS2SResponse(request, code, StrUtil.format(template, args));
    }

    // ---------------------- 私有工具方法 ----------------------

    /**
     * 模板格式化工具（支持命名占位符）
     */
    private static String formatTemplate(String template, Map<String, Object> context) {
        String result = template;
        for (Map.Entry<String, Object> entry : context.entrySet()) {
            String placeholder = "{" + entry.getKey() + "}";
            result = result.replace(placeholder, String.valueOf(entry.getValue()));
        }
        return result;
    }
}